package com.cangjie.xiaozhi

import com.intellij.openapi.editor.Document
import com.intellij.openapi.editor.Editor
import com.intellij.openapi.editor.SelectionModel
import com.intellij.openapi.editor.CaretModel
import com.intellij.openapi.editor.LogicalPosition
import org.junit.Test
import org.junit.Assert.*
import org.mockito.Mockito.*

class SendToXiaoZhiActionTest {
    
    @Test
    fun `test getSelectedTextOrLine with selected text`() {
        // 准备测试数据
        val action = SendToXiaoZhiAction()
        val editor = mock(Editor::class.java)
        val selectionModel = mock(SelectionModel::class.java)
        val selectedText = "    val x = 10    "
        
        // 设置mock行为
        `when`(editor.selectionModel).thenReturn(selectionModel)
        `when`(selectionModel.selectedText).thenReturn(selectedText)
        
        // 使用反射调用私有方法
        val method = SendToXiaoZhiAction::class.java.getDeclaredMethod("getSelectedTextOrLine", Editor::class.java)
        method.isAccessible = true
        val result = method.invoke(action, editor) as String?
        
        // 验证结果
        assertEquals("val x = 10", result)
    }
    
    @Test
    fun `test getSelectedTextOrLine with no selection but valid line`() {
        // 准备测试数据
        val action = SendToXiaoZhiAction()
        val editor = mock(Editor::class.java)
        val selectionModel = mock(SelectionModel::class.java)
        val caretModel = mock(CaretModel::class.java)
        val document = mock(Document::class.java)
        val logicalPosition = LogicalPosition(0, 0)
        val lineText = "    val y = 20    "
        
        // 设置mock行为
        `when`(editor.selectionModel).thenReturn(selectionModel)
        `when`(selectionModel.selectedText).thenReturn(null)
        `when`(editor.caretModel).thenReturn(caretModel)
        `when`(caretModel.logicalPosition).thenReturn(logicalPosition)
        `when`(editor.document).thenReturn(document)
        `when`(document.lineCount).thenReturn(5)
        `when`(document.getLineStartOffset(0)).thenReturn(0)
        `when`(document.getLineEndOffset(0)).thenReturn(lineText.length)
        `when`(document.getText()).thenReturn(lineText)
        
        // 使用反射调用私有方法
        val method = SendToXiaoZhiAction::class.java.getDeclaredMethod("getSelectedTextOrLine", Editor::class.java)
        method.isAccessible = true
        val result = method.invoke(action, editor) as String?
        
        // 验证结果
        assertEquals("val y = 20", result)
    }
    
    @Test
    fun `test getSelectedTextOrLine with empty editor`() {
        // 准备测试数据
        val action = SendToXiaoZhiAction()
        
        // 使用反射调用私有方法
        val method = SendToXiaoZhiAction::class.java.getDeclaredMethod("getSelectedTextOrLine", Editor::class.java)
        method.isAccessible = true
        val result = method.invoke(action, null as Editor?)
        
        // 验证结果
        assertNull(result)
    }
    
    @Test
    fun `test getSelectedTextOrLine with invalid line number`() {
        // 准备测试数据
        val action = SendToXiaoZhiAction()
        val editor = mock(Editor::class.java)
        val selectionModel = mock(SelectionModel::class.java)
        val caretModel = mock(CaretModel::class.java)
        val logicalPosition = LogicalPosition(10, 0) // 无效行号
        
        // 设置mock行为
        `when`(editor.selectionModel).thenReturn(selectionModel)
        `when`(selectionModel.selectedText).thenReturn(null)
        `when`(editor.caretModel).thenReturn(caretModel)
        `when`(caretModel.logicalPosition).thenReturn(logicalPosition)
        `when`(editor.document).thenReturn(mock(Document::class.java))
        `when`(editor.document.lineCount).thenReturn(5) // 只有5行但请求第10行
        
        // 使用反射调用私有方法
        val method = SendToXiaoZhiAction::class.java.getDeclaredMethod("getSelectedTextOrLine", Editor::class.java)
        method.isAccessible = true
        val result = method.invoke(action, editor) as String?
        
        // 验证结果
        assertNull(result)
    }
}